#include "time.h"
#include "kernel.h"
//Time.c
/* Sys Tick counter */
static volatile unsigned int OSTicks = 0;


void OSTick(void){
	TCB *tmp;
	struct list_head *iter;	
//228.95908927	
//228.96008931
//228.96108888
    interruptEnter();
	
	/* increase tick counter*/
	OSTicks++;
	/* check task list for delayed tasks*/
	ENTER_CRITICAL();
	list_for_each(iter, &allTasksLinked){
		tmp = list_entry(iter, TCB, delay_list);
		/* is anyone delayed?*/
		if (tmp->delay != 0){
			/* tick 'im */
			tmp->delay--;
			/* if someone is expired */
			if(tmp->delay == 0){
				TaskArray[tmp->prio]->state = READY;
				/* event state is checked to see if 
				there are any tasks waiting for an event
				with timeout */
				if(tmp->estate != NONE){
					/* if so, change estate */
					tmp->estate = TIMED_OUT;
				}
				/* update Bitmap */
#if HIGHEST_PRIO_ALT == 1
				ReadyArray[tmp->prio] = TaskArray[tmp->prio];
#elif HIGHEST_PRIO_ALT == 2
				ReadyTaskBitmap[(tmp->prio >> 5)] |= 1 << (tmp->prio & 0x1F);								
				ReadyTaskIndex |= 1 << (tmp->prio >> 5);
#elif HIGHEST_PRIO_ALT == 3
				ReadyTaskBitmap |= 1 << (tmp->prio & 0x1F);
#endif
			}
		}
		
	}
	//228.95909253
	//228.96009477
	//228.96109434
	EXIT_CRITICAL();//0.10919025, 0.13419100
	interruptExit();
}//0.10925325,  , 0.13425400
/* but the way, to ipmlement this you'll need:
   a) TCB linked list with all the created task's TCBs
   b) Interrupt enter and interrupt exit functions to be called on every interrupt
	  entry and exit
*/
void TickTasks(void){
	;
}
/*almost just as yield()*/
void timeDelay(uint_32 ticks){
	
	ENTER_CRITICAL();

	currentTCB->delay = ticks;
	currentTCB->state = BLOCKED;

#if HIGHEST_PRIO_ALT == 1
	ReadyArray[currentTCB->prio] = NULL;
#elif HIGHEST_PRIO_ALT == 2
	ReadyTaskBitmap[(currentTCB->prio >> 5)] &=  ~(1 << (currentTCB->prio & 0x1F)) ;	
	ReadyTaskIndex &= ~(1 >> currentTCB->prio >> 5);
#elif HIGHEST_PRIO_ALT == 3
	ReadyTaskBitmap &=  ~(1 << (currentTCB->prio & 0x1F)) ;
#endif
	EXIT_CRITICAL();
	schedule();
}

uint_32 getTickCount(void)
{
	return OSTicks;
}